﻿using System.Collections;
using System.Collections.Generic;
using System.Text;
using System.Xml;
using System.Xml.Xsl;
using System.Xml.XPath;
using System.Web;
using System.IO;
//using SBS.Base;
using System;

namespace AppEntity
{
    public partial class Common
    {
        /// <summary>
        /// 转换类
        /// </summary>
        public class Convert
        {
            /// <summary>
            /// 转换XML为HTML
            /// </summary>
            /// <param name="xmlstring">XML数据，可以是文件路径，也可以是XML字符串</param>
            /// <param name="xslpath">XSL 文件路径</param>
            /// <param name="param">转换过程接收的参数，Hashtable 将转换为 XsltArgumentList。</param>
            /// <returns>返回html字符串</returns>
            public static string xml2html(string xmlstring, string xslpath, Hashtable param, bool NoSysNode)
            {
                return xml2html(xmlstring, GetXslProcessInMemory(xslpath), param, NoSysNode);
            }
            public static string xml2html(string xmlstring, XslCompiledTransform XslProcess, Hashtable param, bool NoSysNode)
            {


                //XmlReaderSettings xrsetting = new XmlReaderSettings();
                //xrsetting.ProhibitDtd = false;
                //xrsetting.XmlResolver = new XmlUrlResolver();
                //xrsetting.IgnoreComments = true;
                //xrsetting.IgnoreWhitespace = true;


                XmlDocument dom = new XmlDocument();

                if (xmlstring.Trim().Substring(0, 1) == "<")
                {
                    dom.LoadXml(xmlstring);
                }
                else
                {
                    dom.Load(xmlstring);
                }
                return xml2html(dom, XslProcess, param, NoSysNode);

                //if (HttpContext.Current != null && HttpContext.Current.Request.QueryString["output"] == "xml")
                //{
                //    HttpContext.Current.Response.ContentType = "text/xml";
                //    return dom.OuterXml;
                //}
                //if (NoSysNode != true)
                //{
                //    if (dom.DocumentElement.SelectSingleNode("system") != null)
                //    {
                //        dom.DocumentElement.RemoveChild(dom.DocumentElement.SelectSingleNode("system"));
                //    }
                //    dom.DocumentElement.AppendChild(GetSystemNode(dom));
                //}

                //if (HttpContext.Current != null)
                //{
                //    if (!string.IsNullOrEmpty(HttpContext.Current.Request.QueryString["debug"]) && HttpContext.Current.Request.QueryString["debug"] == "1")
                //    {
                //        HttpContext.Current.Response.ContentType = "text/xml";
                //        HttpContext.Current.Response.Write(dom.OuterXml);
                //        HttpContext.Current.Response.End();
                //        return "";
                //    }
                //}



                //XsltArgumentList argus = new XsltArgumentList();

                //if (param == null)
                //{
                //    param = new Hashtable();
                //}

                //if (HttpContext.Current != null)
                //{
                //    HttpCookie lang = HttpContext.Current.Request.Cookies["lang"];
                //    if (lang != null && !string.IsNullOrEmpty(lang.Value))
                //    {
                //        if (param.ContainsKey("dictionary"))
                //        {
                //            param["dictionary"] = Utility.GetLangDictionary(lang.Value);
                //        }
                //        else
                //        {
                //            param.Add("dictionary", Utility.GetLangDictionary(lang.Value));
                //        }
                //    }
                //    else
                //    {
                //        if (param.ContainsKey("dictionary"))
                //        {
                //            param["dictionary"] = Utility.GetLangDictionary("zh-cn");
                //        }
                //        else
                //        {
                //            param.Add("dictionary", Utility.GetLangDictionary("zh-cn"));
                //        }
                //    }
                //}
                //foreach (string key in param.Keys)
                //{
                //    if (key.Length > 4 && key.Substring(0, 4) == "urn:")
                //    {
                //        argus.AddExtensionObject(key, param[key]);
                //    }
                //    else
                //    {
                //        argus.AddParam(key, String.Empty, param[key]);
                //    }
                //}
                //XPathNavigator nav = dom.CreateNavigator();
                ////TextWriter html = new StringWriter();
                //MemoryStream ms = new MemoryStream();
                //XslProcess.Transform(nav, argus, ms);


                //ms.Position = 0;

                //StreamReader reader = new StreamReader(ms);
                //string result = reader.ReadToEnd();
                ////string result = html.ToString().Replace("<META http-equiv=\"Content-Type\" content=\"text/html; charset=utf-16\">", "");
                //reader.Close();
                //ms.Close();
                ////html.Close();

                //return result;

            }
            /// <summary>
            /// 转换XML为HTML
            /// </summary>
            /// <param name="dom">XmlDocument 对象</param>
            /// <param name="xslpath">XSL 文件路径</param>
            /// <param name="param">转换过程接收的参数，Hashtable 将转换为 XsltArgumentList。</param>
            /// <returns>返回html字符串</returns>            
            public static string xml2html(XmlDocument dom, string xslpath, Hashtable param, bool NoSysNode)
            {
                return xml2html(dom, GetXslProcessInMemory(xslpath), param, NoSysNode);
            }
            public static byte[] xml2htmlbytes(XmlDocument dom, string xslpath, Hashtable param, bool NoSysNode)
            {
                return xml2htmlbytes(dom, GetXslProcessInMemory(xslpath), param, false);
            }
            public static byte[] xml2htmlbytes(XmlDocument dom, XslCompiledTransform XslProcess, Hashtable param, bool NoSysNode)
            {
                //if (HttpContext.Current != null && HttpContext.Current.Request.QueryString["output"] == "xml")
                //{
                //    HttpContext.Current.Response.ContentType = "text/xml";
                //    return dom.OuterXml;
                //}

                if (NoSysNode != true)
                {
                    if (dom.DocumentElement.SelectSingleNode("system") != null)
                    {
                        dom.DocumentElement.RemoveChild(dom.DocumentElement.SelectSingleNode("system"));
                    }
                    //dom.DocumentElement.AppendChild(XmlTransform.CreateSystemElement(dom));
                    dom.DocumentElement.AppendChild(GetSystemNode(dom));
                }

                if (HttpContext.Current != null)
                {
                    if (!string.IsNullOrEmpty(HttpContext.Current.Request.QueryString["debug"]) && HttpContext.Current.Request.QueryString["debug"] == "1")
                    {
                        HttpContext.Current.Response.ContentType = "text/xml";
                        HttpContext.Current.Response.Write(dom.OuterXml);
                        HttpContext.Current.Response.End();
                        return null;
                    }
                }
                if (HttpContext.Current != null)
                {
                    HttpCookie lang = HttpContext.Current.Request.Cookies["lang"];
                    string langTxt = (lang != null && !string.IsNullOrEmpty(lang.Value)) ? lang.Value : "zh-cn";
                    if (param == null)
                    {
                        param = new Hashtable();
                    }
                    //if (!param.ContainsKey("dictionary"))
                    //{
                    //    param.Add("dictionary", Utility.GetLangDictionary(langTxt));
                    //}
                }
                XmlTransform Xt = new XmlTransform();
                Xt.InputXmlNode = dom;
                Xt.InputXslt = XslProcess;
                Xt.Argus = param;
                return Xt.TransformToBytes();
            }

            public static string xml2html(XmlDocument dom, XslCompiledTransform XslProcess, Hashtable param, bool NoSysNode)
            {
                if (HttpContext.Current != null && HttpContext.Current.Request.QueryString["output"] == "xml")
                {
                    HttpContext.Current.Response.ContentType = "text/xml";
                    return dom.OuterXml;
                }

                if (NoSysNode != true)
                {
                    if (dom.DocumentElement.SelectSingleNode("system") != null)
                    {
                        dom.DocumentElement.RemoveChild(dom.DocumentElement.SelectSingleNode("system"));
                    }
                    //dom.DocumentElement.AppendChild(XmlTransform.CreateSystemElement(dom));
                    dom.DocumentElement.AppendChild(GetSystemNode(dom));
                }

                if (HttpContext.Current != null)
                {
                    if (!string.IsNullOrEmpty(HttpContext.Current.Request.QueryString["debug"]) && HttpContext.Current.Request.QueryString["debug"] == "1")
                    {
                        HttpContext.Current.Response.ContentType = "text/xml";
                        HttpContext.Current.Response.Write(dom.OuterXml);
                        HttpContext.Current.Response.End();
                        return "";
                    }
                }
                if (HttpContext.Current != null)
                {
                    HttpCookie lang = HttpContext.Current.Request.Cookies["lang"];
                    string langTxt = (lang != null && !string.IsNullOrEmpty(lang.Value)) ? lang.Value : "zh-cn";
                    if (param == null)
                    {
                        param = new Hashtable();
                    }
                    //if (!param.ContainsKey("dictionary"))
                    //{
                    //    param.Add("dictionary", Utility.GetLangDictionary(langTxt));
                    //}
                }
                XmlTransform Xt = new XmlTransform();
                Xt.InputXmlNode = dom;
                Xt.InputXslt = XslProcess;
                Xt.Argus = param;
                return Xt.TransformToString();


                //XsltArgumentList argus = new XsltArgumentList();

                //if (param == null)
                //{
                //    param = new Hashtable();
                //}

                //if (HttpContext.Current != null)
                //{
                //    HttpCookie lang = HttpContext.Current.Request.Cookies["lang"];
                //    if (lang != null && !string.IsNullOrEmpty(lang.Value))
                //    {
                //        if (param.ContainsKey("dictionary"))
                //        {
                //            param["dictionary"] = Utility.GetLangDictionary(lang.Value);
                //        }
                //        else
                //        {
                //            param.Add("dictionary", Utility.GetLangDictionary(lang.Value));
                //        }
                //    }
                //    else
                //    {
                //        if (param.ContainsKey("dictionary"))
                //        {
                //            param["dictionary"] = Utility.GetLangDictionary("zh-cn");
                //        }
                //        else
                //        {
                //            param.Add("dictionary", Utility.GetLangDictionary("zh-cn"));
                //        }
                //    }
                //}

                //foreach (string key in param.Keys)
                //{
                //    if (key.Length > 4 && key.Substring(0, 4) == "urn:")
                //    {
                //        argus.AddExtensionObject(key, param[key]);
                //    }
                //    else
                //    {
                //        argus.AddParam(key, String.Empty, param[key]);
                //    }
                //}

                //XPathNavigator nav = dom.CreateNavigator();
                //MemoryStream ms = new MemoryStream();
                //XslProcess.Transform(nav, argus, ms);

                //ms.Position = 0;
                //StreamReader reader = new StreamReader(ms);
                //string html = reader.ReadToEnd();
                //reader.Close();
                //ms.Close();
                //return html;

            }
            /// <summary>
            /// 转换XML为HTML
            /// </summary>
            /// <param name="xmlstring">XML数据，可以是文件路径，也可以是XML字符串</param>
            /// <param name="xslpath">XSL 文件路径</param>
            /// <returns>返回html字符串</returns>
            public static string xml2html(XmlDocument dom, string xslpath)
            {
                return xml2html(dom, xslpath, null, false);
            }
            public static string xml2html(XmlDocument dom, string xslpath, Hashtable param)
            {
                return xml2html(dom, xslpath, param, false);
            }
            public static string xml2html(string xmlstring, string xslpath)
            {
                return xml2html(xmlstring, xslpath, null, false);
            }
            public static string xml2html(string xmlstring, string xslpath, bool NoSysNode)
            {
                return xml2html(xmlstring, xslpath, null, NoSysNode);
            }
            public static string xml2html(string xmlstring, string xslpath, Hashtable param)
            {
                return xml2html(xmlstring, xslpath, param, false);
            }

            public static string xml2html(XPathNavigator nav, string xslcode, Hashtable param)
            {
                XmlTransform Xt = new XmlTransform();
                Xt.InputXmlNode = nav;
                Xt.InputXsltCode = xslcode;
                Xt.Argus = param;
                return Xt.TransformToString();

                //XmlReaderSettings xrsetting = new XmlReaderSettings();
                //xrsetting.ProhibitDtd = false;
                //xrsetting.XmlResolver = new XmlUrlResolver();
                //xrsetting.IgnoreComments = true;
                //xrsetting.IgnoreWhitespace = true;

                //StringReader sr = new StringReader(xslcode);

                //XmlReader xr = XmlReader.Create(sr, xrsetting);
                //XslCompiledTransform process = new XslCompiledTransform();
                //XsltSettings setting = new XsltSettings(true, true);

                //XmlUrlResolver resolver = new XmlUrlResolver();
                //resolver.Credentials = System.Net.CredentialCache.DefaultCredentials;

                //XsltArgumentList argus = new XsltArgumentList();
                //foreach (string key in param.Keys)
                //{
                //    if (key.Length > 4 && key.Substring(0, 4) == "urn:")
                //    {
                //        argus.AddExtensionObject(key, param[key]);
                //    }
                //    else
                //    {
                //        argus.AddParam(key, String.Empty, param[key]);
                //    }
                //}
                //try
                //{
                //    process.Load(xr, setting, resolver);
                //    MemoryStream Stream = new MemoryStream();
                //    process.Transform(nav, argus, Stream);
                //    Stream.Flush();
                //    Stream.Position = 0;
                //    StreamReader sreader = new StreamReader(Stream);
                //    string html = sreader.ReadToEnd();
                //    sreader.Close();
                //    Stream.Close();
                //    return html;
                //}
                //catch (Exception ex)
                //{
                //    return null;
                //}
                //finally
                //{
                //    xr.Close();
                //}
            }

            public static string xml2text(string xmlstring, string xslpath, Hashtable param, bool NoSysNode)
            {
                return xml2html(xmlstring, xslpath, param, true);
            }
            public static string xml2text(string xmlstring, string xslpath)
            {
                return xml2html(xmlstring, xslpath, null, true);
            }
            public static string xml2text(XmlDocument dom, string xslpath, Hashtable param, bool NoSysNode)
            {
                return xml2html(dom, xslpath, param, true);
            }
            public static string xml2text(XmlDocument dom, string xslpath)
            {
                return xml2html(dom, xslpath, null, true);
            }
            public static string xml2text(XmlDocument dom, string xslpath, bool NoSysNode)
            {
                return xml2html(dom, xslpath, null, NoSysNode);
            }
            public static XmlNode GetSystemNode(XmlDocument dom)
            {
                XmlElement sys = dom.CreateElement("system");
                XmlElement url = dom.CreateElement("url");
                XmlElement http = dom.CreateElement("http");
                XmlElement cookies = dom.CreateElement("cookies");
                XmlElement variable = dom.CreateElement("variable");

                if (HttpContext.Current != null)
                {
                    foreach (string key in HttpContext.Current.Request.QueryString)
                    {

                        if (key != null && key.Length > 0 && "0123456789".IndexOf(key.Substring(0, 1)) == -1)
                        {
                            try
                            {
                                if (!string.IsNullOrEmpty(HttpContext.Current.Request.QueryString[key]))
                                {
                                    url.SetAttribute(key.ToLower(), HttpContext.Current.Request.QueryString[key]);
                                }
                                else
                                {
                                    url.SetAttribute(key.ToLower(), "");
                                }

                            }
                            catch (Exception ex)
                            {
                                //随机数显示有问题
                            }
                        }
                    }

                    foreach (string key in HttpContext.Current.Request.Cookies.AllKeys)
                    {

                        if (key != null && key.Length > 0 && "0123456789".IndexOf(key.Substring(0, 1)) == -1)
                        {
                            XmlAttribute attr = dom.CreateAttribute(key);

                            if (key == "timezone")
                            {
                                attr.Value = HttpContext.Current.Request.Cookies[key].Value;
                            }
                            else
                            {
                                attr.Value = HttpContext.Current.Server.UrlDecode(HttpContext.Current.Request.Cookies[key].Value);
                            }
                            cookies.SetAttributeNode(attr);
                        }
                    }
                }
                if (HttpContext.Current != null && HttpContext.Current.Request.UserLanguages != null)
                {
                    variable.SetAttribute("lang", string.Join(",", HttpContext.Current.Request.UserLanguages));
                }
                variable.SetAttribute("servertime", AppEntity.Common.Utility.GetNowTime());
                http.AppendChild(cookies);
                http.AppendChild(variable);
                sys.AppendChild(url);
                sys.AppendChild(http);
                return sys;
            }
            //private static XslCompiledTransform GetXslProcessInMemory(string xslkey)
            //{
            //    string LastWriteTime = File.GetLastWriteTime(xslkey).ToString("yyyy-MM-ddTHH:mm:ss.fffK");
            //    string key = LastWriteTime + xslkey;

            //    if (HttpContext.Current.Application[LastWriteTime + xslkey] == null || HttpContext.Current.Request.QueryString["debug"] == "3")
            //    {
            //        XmlReaderSettings xrsetting = new XmlReaderSettings();
            //        xrsetting.ProhibitDtd = false;
            //        xrsetting.XmlResolver = new XmlUrlResolver();
            //        xrsetting.IgnoreComments = true;
            //        xrsetting.IgnoreWhitespace = true;

            //        XmlReader xr = XmlReader.Create(xslkey, xrsetting);
            //        XslCompiledTransform process = new XslCompiledTransform();

            //        XsltSettings setting = XsltSettings.TrustedXslt;
            //        setting.EnableDocumentFunction = true;
            //        setting.EnableScript = true;

            //        XmlUrlResolver resolver = new XmlUrlResolver();
            //        resolver.Credentials = System.Net.CredentialCache.DefaultCredentials;

            //        try
            //        {
            //            process.Load(xr, setting, resolver);
            //        }
            //        catch (Exception ex)
            //        {
            //            return null;
            //        }
            //        finally
            //        {
            //            xr.Close();
            //        }

            //        string[] removeKey = new string[HttpContext.Current.Application.AllKeys.Length];
            //        int i = 0;
            //        foreach (string appkey in HttpContext.Current.Application.AllKeys)
            //        {
            //            if (appkey.Length <= 29) continue;
            //            if (appkey.Substring(29) == xslkey)
            //            {
            //                removeKey[i++] = appkey;
            //            }
            //        }
            //        HttpContext.Current.Application.Lock();
            //        foreach (string k in removeKey)
            //        {
            //            HttpContext.Current.Application.Remove(k);
            //        }
            //        HttpContext.Current.Application.UnLock();

            //        HttpContext.Current.Application[LastWriteTime + xslkey] = process;
            //    }
            //    return (XslCompiledTransform)HttpContext.Current.Application[LastWriteTime + xslkey];
            //}
            public static XslCompiledTransform GetXslProcessInMemory(string xslkey)
            {
                return XmlTransform.GetXslProcessInMemory(xslkey);
                /////////////////////////////////////////////////////////////////


                //if (HttpRuntime.Cache[xslkey] != null)
                //{
                //    //return (XslCompiledTransform)HttpRuntime.Cache[xslkey];
                //}

                //XmlReaderSettings xrsetting = new XmlReaderSettings();
                //xrsetting.ProhibitDtd = false;
                //xrsetting.XmlResolver = new XmlUrlResolver();
                //xrsetting.IgnoreComments = true;
                //xrsetting.IgnoreWhitespace = true;

                //XmlReader xr = XmlReader.Create(xslkey, xrsetting);
                //XslCompiledTransform process = new XslCompiledTransform();

                //XsltSettings setting = XsltSettings.TrustedXslt;
                //setting.EnableDocumentFunction = true;
                //setting.EnableScript = true;

                //XmlUrlResolver resolver = new XmlUrlResolver();
                //resolver.Credentials = System.Net.CredentialCache.DefaultCredentials;

                //try
                //{
                //    process.Load(xr, setting, resolver);
                //}
                //catch (Exception ex)
                //{
                //    return null;
                //}
                //finally
                //{
                //    xr.Close();
                //}

                //System.Web.Caching.CacheDependency dep = new System.Web.Caching.CacheDependency(xslkey);
                //HttpRuntime.Cache.Insert(xslkey, process, dep);
                //return (XslCompiledTransform)HttpRuntime.Cache[xslkey];

            }
        }
    }

}
